-- Copyright (c) 2015,2016 Lucky Byte, Inc.
--
-- Summary : 查询银联 ACP 交易结果
--
-- Author  : 吴小虎 <xiaohu@lucky-byte.com>
-- Since   : 2016.6.17
--
-- History
--  * 2016.6.17 : 创建此文件
--  * 2016.7.12 : 更新消费代付订单状态
--  * 2016.7.27 : 若查询交易响应 03, 04, 05，则稍后再次查询
--  * 2016.8.02 : 查询结果排序，先到的交易先处理
--
require "core.lib"

-- 查询一条当天 5 分钟后尚未接收到后台通知的 ACP 交易流水
--
local _table = jdbc.select([[
    select *,
        json_extract_path_text(i_pkt, 'merId') as merid,
        json_extract_path_text(i_pkt, 'orderId') as order_id,
        json_extract_path_text(i_pkt, 'txnTime') as txn_time
    from pay_trlist
    where
        sys_time::date = CURRENT_DATE and
        sys_time::time < CURRENT_TIME - interval '5 minutes' and
        incoming = false and chnl = 3 and n_pkt is NULL and
        json_extract_path_text(i_pkt, 'txnType') in ( '12' )
    order by serial limit 1
]])
-- 如果没有这样的记录，直接返回
if _table.count == 0 then
    logger.trace('没有查询到未收到通知的 ACP 交易，无需处理...')
    return
end
local _acp_record = _table.get_record(0)

-- 查询原交易商户信息
--
local _acp_merid = _acp_record.get('merid')
local _table = jdbc.select([[
    select * from pay_merch where chnl = 3 and merno = ?
]], _acp_merid)
if _table.count == 0 then
    logger.error('系统内未查询到原 ACP 交易商户[%s]的信息.', _merch.merno)
    return
end
local _merch = _table.get_record(0)

logger.info('检查到银联 ACP 交易[%s]尚未收到通知报文，开始查询此交易结果...',
    _acp_record.get('uuid'))

-- 构造一个 ACP 查询交易报文，并发送到银联进行处理
--
local _071_packet = lib071.new_packet()

_071_packet.set('txnType', '00')
_071_packet.set('txnSubType', '00')
_071_packet.set('bizType', '000401')
_071_packet.set('accessType', '0')
_071_packet.set('merId', _acp_merid)

-- 设置查询条件(原交易时间和订单号)
_071_packet.set('txnTime', _acp_record.get('txn_time'))
_071_packet.set('orderId', _acp_record.get('order_id'))

-- 发送查询交易报文
local _fowd = lib071.forward({
    uuid = uuid(), indirect = true, packet = _071_packet, merch = _merch
})
if not _fowd or not _fowd.respkt then
    logger.error('银联 ACP 查询交易失败，不更新原交易流水.')
    return
end

local _resp_ok = lib071.respkt_ok(_fowd.respkt)
if _resp_ok then
    logger.info('查询原 ACP 交易结果成功，原交易响应[%s: %s].',
        _fowd.respkt.get('origRespCode') or '',
        _fowd.respkt.get('origRespMsg') or '')
else
    logger.warn('银联 ACP 查询交易响应失败[%s: %s].', lib071.rescode(_fowd.respkt))

    -- 若收到 respCode 为 03、04、05 的应答时，则需要再次发起交易查询
    local _rescode = _fowd.respkt.get('respCode')
    if table.hasv({'03', '04', '05'}, _rescode) then return end
end

-- 使用原交易响应码替代查询交易响应码(如果存在的话)
--
if _fowd.respkt.has('origRespCode') then
    _fowd.respkt.set('respCode', _fowd.respkt.get('origRespCode'))
end
if _fowd.respkt.has('origRespMsg') then
    _fowd.respkt.set('respMsg', _fowd.respkt.get('origRespMsg'))
end

-- 更新原交易记录流水通知报文及备注
--
local _rescode, _resmsg = lib071.rescode(_fowd.respkt)
local _notes = _resp_ok and '查询结果：' or '查询失败：'
local _notes = _notes .. _rescode .. '-' .. _resmsg
jdbc.update([[
    update pay_trlist set n_pkt = ?, notes = ? where uuid = ? and uuid_no = ?
]],
    _fowd.respkt.tojson(), _notes,
    _acp_record.get('uuid'), _acp_record.get('uuid_no')
)
logger.info('更新原 ACP 交易流水成功...')


-- 如果原交易与代付订单关联，则更新订单状态
-- 同时也更新追付纪录
--
core.acp_aux.update_p1_order (_acp_record.get('uuid'), _rescode)
core.acp_aux.update_p2_order (_acp_record.get('uuid'), _rescode)
core.acp_aux.update_t40_recvr(_acp_record.get('uuid'), _rescode)
